package drds.common.db.xml_mapping.script.defaults;

import drds.common.db.xml_mapping.executor.parameter.ParameterHandler;
import drds.common.db.xml_mapping.mapping.BindSql;
import drds.common.db.xml_mapping.mapping.Mapper;
import drds.common.db.xml_mapping.mapping.ParameterMapping;
import drds.common.db.xml_mapping.parameter_and_result_value_type.JdbcType;
import drds.common.db.xml_mapping.parameter_and_result_value_type.TypeHandlerRegistry;
import drds.common.db.xml_mapping.reflection.MetaObject;
import drds.common.db.xml_mapping.session.Configuration;

import java.sql.PreparedStatement;
import java.util.List;


public class DefaultParameterHandler implements ParameterHandler {

  private final TypeHandlerRegistry typeHandlerRegistry;

  private final Mapper mapper;
  private final Object parameterObject;
  private final BindSql bindSql;
  private final Configuration configuration;

  public DefaultParameterHandler(Mapper mapper, Object parameterObject, BindSql bindSql) {
    this.mapper = mapper;
    this.configuration = mapper.getConfiguration();
    this.typeHandlerRegistry = mapper.getConfiguration().getTypeHandlerRegistry();
    this.parameterObject = parameterObject;
    this.bindSql = bindSql;
  }

  @Override
  public Object getParameterObject() {
    return parameterObject;
  }

  @Override
  public void setParameters(PreparedStatement preparedStatement) {

    List<ParameterMapping> parameterMappingList = bindSql.getParameterMappingList();
    if (parameterMappingList != null) {
      for (int i = 0; i < parameterMappingList.size(); i++) {
        ParameterMapping parameterMapping = parameterMappingList.get(i);
        {
          Object value;
          String propertyName = parameterMapping.getPropertyName();
          if (bindSql.hasAdditionalParameter(propertyName)) {
            value = bindSql.getAdditionalParameter(propertyName);
          } else if (parameterObject == null) {
            value = null;
          } else if (typeHandlerRegistry.hasTypeHandler(parameterObject.getClass())) {
            value = parameterObject;
          } else {
            MetaObject metaObject = configuration.newMetaObject(parameterObject);
            value = metaObject.getValue(propertyName);
          }

          JdbcType jdbcType = parameterMapping.getJdbcType();
          if (value == null && jdbcType == null) {
            jdbcType = configuration.getJdbcTypeForNull();
          }

        }
      }
    }
  }

}
